/**
 * @copyright 2017 sinping.com 北京芯平科技股份有限公司. All rights reserved.
 * 本内容仅限于北京芯平科技股份有限公司内部传阅，禁止外泄以及用于其他的商业目的.
 */
package com.sinping.qh.api.auth;


import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.baomidou.mybatisplus.plugins.Page;
import com.sinping.qh.api.support.Const;
import com.sinping.qh.api.support.ConstEum;
import com.sinping.qh.api.support.FrontPage;
import com.sinping.qh.api.support.ResDto;
import com.sinping.qh.domain.auth.Role;
import com.sinping.qh.domain.auth.UserRole;
import com.sinping.qh.dto.auth.RoleDTO;
import com.sinping.qh.service.admin.IAddorEditUserService;
import com.sinping.qh.service.auth.IRoleService;
import com.sinping.qh.service.auth.IUserRoleService;
import com.sinping.qh.utils.mapper.BeanMapper;
import com.sinping.qh.utils.mapper.JsonMapper;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.DataIntegrityViolationException;
import org.springframework.web.bind.annotation.*;

import java.util.List;

/**
 * <p>
 * 前端控制器
 * </p>
 *
 * @author 刘庆沛
 * @since 2017-12-18
 */
@Api(value = "Admin角色管理", description = "Admin角色管理API")
@RestController
@RequestMapping(value = Const.BASE_URI + "role", name = "角色管理")
public class RoleEndPoint {

    private final static Logger logger = LoggerFactory.getLogger(RoleEndPoint.class);

    @Autowired
    private IRoleService roleService;

    @Autowired
    private IUserRoleService userRoleService;
    @Autowired
    private IAddorEditUserService iAddorEditUserService;


    @ApiOperation(value = "角色列表", notes = "不传参时查询所有角色，或者传参分页")
    @RequestMapping(method = RequestMethod.GET, name = "角色列表")
    public ResDto listPage(@ApiParam(name = "msg", value = "{\"page_size\":10,\"page_current\":1,\"order_column\":null,\"order_by\":null}", required = true)
                           @RequestParam(required = true) String msg) {
        try {
            String result = null;

            FrontPage<Role> page = JsonMapper.defaultMapper().fromJson(msg, FrontPage.class);
            if(page == null){
                logger.error("参数为空或有不正确的数据格式");
                return new ResDto(Const.PARAM_ERROR, "msg.param.error");
            }

            if (page.getPage() == 0) {
                Wrapper<Role> wrapper = new EntityWrapper<>();
                if(StringUtils.isBlank(page.getProp())){
                    wrapper.orderBy("create_time", false);
                }
                List<Role> roles = roleService.selectList(wrapper);
                List<RoleDTO> roleDTOS = BeanMapper.mapList(roles, RoleDTO.class);
                FrontPage frontPage = new FrontPage<RoleDTO>();
                frontPage.setRecords(roleDTOS);
                result = JsonMapper.defaultMapper().toJson(frontPage);
            } else {
                Page rolePage = roleService.selectPage(page.toPagePlus());
                List list = BeanMapper.mapList(rolePage.getRecords(), RoleDTO.class);
                rolePage.setRecords(list);
                result = JsonMapper.defaultMapper().toJson(new FrontPage(rolePage));
            }
            return new ResDto(ConstEum.SUCCESS, result);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            return new ResDto(ConstEum.SERVER_ERROR);
        }
    }

    @ApiParam(name = "id")
    @ApiOperation(value = "获取角色", notes = "参数：角色id")
    @RequestMapping(value = "/${id}", method = RequestMethod.GET, name = "获取角色")
    public ResDto getById(@PathVariable String id) {
        try {
            Role role = roleService.selectById(id);
            RoleDTO roleDTO = BeanMapper.map(role, RoleDTO.class);
            return new ResDto(ConstEum.SUCCESS, JsonMapper.defaultMapper().toJson(roleDTO));
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            return new ResDto(ConstEum.SERVER_ERROR);
        }
    }

    /**
     * update by 陈长石：
     * 由于角色修改提交的参数较大，放到查询串中导致请求URL过长，改为Post方式，参数放到请求体中
     *
     * @param msg
     * @return
     */
    @ApiOperation(value = "角色更新")
    @RequestMapping(value = "/update", method = RequestMethod.POST, name = "角色更新")
    public ResDto update(@ApiParam(name = "msg", value = "{\"id\":null,\"role\":null,\"status\":null,\"security\":null,\"permission\":null,\"desc\":null,<br>\"resources\":null}")
                         @RequestParam String msg) {
        try {
            RoleDTO roleDTO = JsonMapper.defaultMapper().fromJson(msg, RoleDTO.class);
            if(roleDTO == null){
                logger.error("参数为空或有不正确的数据格式");
                return new ResDto(Const.PARAM_ERROR, "参数为空或有不正确的数据格式");
            }
            if (StringUtils.isEmpty(roleDTO.getId())){
                logger.error("ID不能为空");
                return new ResDto(Const.PARAM_ERROR, "角色ID不能为空");
            }
            if (StringUtils.isEmpty(roleDTO.getRole())) {
                return new ResDto(Const.PARAM_ERROR, "角色名不能为空");
            }
            if (StringUtils.isEmpty(roleDTO.getPermission())) {
                return new ResDto(Const.PARAM_ERROR, "app权限不能为空");
            }
            if (StringUtils.isEmpty(roleDTO.getSecurity())){
                logger.error("security不能为空");
                return new ResDto(Const.PARAM_ERROR, "安全员标识不能为空");
            }


            Role role = BeanMapper.map(roleDTO, Role.class);
            Role roleDB = roleService.selectById(role.getId());
            boolean update = roleService.updateById(role);
            //更新
            if (update){
                iAddorEditUserService.findUserByRoleId(role,roleDB);
            }
            return new ResDto(ConstEum.SUCCESS);
        } catch (DataIntegrityViolationException e) {
            logger.error(e.getMessage(), e);
            throw e;
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            return new ResDto(ConstEum.SERVER_ERROR);
        }
    }

    @ApiOperation("角色新增")
    @RequestMapping(method = RequestMethod.POST, name = "角色新增")
    public ResDto add(@ApiParam(name = "msg", value = "{\"role\":null,\"status\":null,\"security\":null,\"desc\":null,<br>\"permission\":null}")
                      @RequestParam String msg) {
        try {
            RoleDTO roleDTO = JsonMapper.defaultMapper().fromJson(msg, RoleDTO.class);
            if(roleDTO == null){
                logger.error("参数为空或有不正确的数据格式");
                return new ResDto(Const.PARAM_ERROR, "msg.param.error");
            }
            Role role = BeanMapper.map(roleDTO, Role.class);
            if (role == null) {
                return new ResDto(Const.PARAM_ERROR, "msg.add.fail");
            }
            if (StringUtils.isEmpty(role.getRole())) {
                return new ResDto(Const.PARAM_ERROR, "角色名不能为空");
            }
            if (StringUtils.isEmpty(role.getPermission())) {
                return new ResDto(Const.PARAM_ERROR, "app权限不能为空");
            }
            if (StringUtils.isEmpty(role.getSecurity())) {
                return new ResDto(Const.PARAM_ERROR, "安全员标识不能为空");
            }
            roleService.insertRoleAndRoleResource(role);
            return new ResDto(ConstEum.SUCCESS);
        } catch (DataIntegrityViolationException e) {
            logger.error(e.getMessage(), e);
            throw e;
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            return new ResDto(ConstEum.SERVER_ERROR);
        }
    }

    @ApiParam(name = "id")
    @ApiOperation(value = "角色删除、物理删除", notes = "参数：角色id")
    @RequestMapping(value = "/{id}", method = RequestMethod.DELETE, name = "角色删除、物理删除")
    public ResDto delete(@ApiParam(name = "id", value = "245ad13d6ad4") @PathVariable(required = true) String id) {
        try {
            if (StringUtils.isEmpty(id)) {
                return new ResDto(Const.PARAM_ERROR, "角色id不能为空");
            }
            List<UserRole> userRoles = userRoleService.selectEffectiveUserRoleByRoleId(id);
            if (userRoles != null && userRoles.size() > 0) {
                return new ResDto(Const.PARAM_ERROR, "角色已配置权限资源，请先删除");
            }
            roleService.deleteById(id);
            return new ResDto(ConstEum.SUCCESS);
        } catch (DataIntegrityViolationException e) {
            logger.error(e.getMessage(), e);
            throw e;
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            return new ResDto(ConstEum.SERVER_ERROR);
        }
    }


}

